package cyx.example.ddd.application.config;

import lombok.extern.slf4j.Slf4j;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.scheduling.annotation.EnableAsync;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;

import java.util.concurrent.Executor;
import java.util.concurrent.ThreadPoolExecutor;

/**
 * 异步配置类
 * 
 * 注意：这是一个示例实现，在实际企业项目中，可能需要考虑：
 * 1. 线程池大小的调优
 * 2. 线程池监控和指标收集
 * 3. 线程池的优雅关闭
 * 4. 不同业务场景的线程池隔离
 */
@Slf4j
@Configuration
@EnableAsync
public class AsyncConfig {

    /**
     * 配置异步事件处理的线程池
     * 
     * 注意：在实际项目中，可能需要：
     * 1. 根据业务场景配置不同的线程池
     * 2. 监控线程池的使用情况
     * 3. 配置线程池的告警规则
     * 4. 实现线程池的动态调整
     */
    @Bean(name = "eventTaskExecutor")
    public Executor eventTaskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();

        // 核心线程数：处理事件的核心线程数量
        executor.setCorePoolSize(5);

        // 最大线程数：处理事件的最大线程数量
        executor.setMaxPoolSize(20);

        // 队列容量：等待处理的事件队列大小
        executor.setQueueCapacity(100);

        // 线程名前缀：便于日志追踪
        executor.setThreadNamePrefix("EventAsync-");

        // 线程空闲时间：超过核心线程数的线程空闲多久后回收
        executor.setKeepAliveSeconds(60);

        // 拒绝策略：当线程池和队列都满时的处理策略
        executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());

        // 等待所有任务结束后再关闭线程池
        executor.setWaitForTasksToCompleteOnShutdown(true);

        // 等待时间：等待任务完成的最大时间
        executor.setAwaitTerminationSeconds(60);

        // 初始化线程池
        executor.initialize();

        log.info("事件处理线程池初始化完成 - 核心线程数: {}, 最大线程数: {}, 队列容量: {}",
                executor.getCorePoolSize(), executor.getMaxPoolSize(), executor.getQueueCapacity());

        return executor;
    }

    /**
     * 配置通用异步处理的线程池
     */
    @Bean(name = "taskExecutor")
    public Executor taskExecutor() {
        ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();

        executor.setCorePoolSize(10);
        executor.setMaxPoolSize(50);
        executor.setQueueCapacity(200);
        executor.setThreadNamePrefix("Async-");
        executor.setKeepAliveSeconds(60);
        executor.setRejectedExecutionHandler(new ThreadPoolExecutor.CallerRunsPolicy());
        executor.setWaitForTasksToCompleteOnShutdown(true);
        executor.setAwaitTerminationSeconds(60);

        executor.initialize();

        log.info("通用异步处理线程池初始化完成 - 核心线程数: {}, 最大线程数: {}, 队列容量: {}",
                executor.getCorePoolSize(), executor.getMaxPoolSize(), executor.getQueueCapacity());

        return executor;
    }
}